﻿#Include ..\baseHandle.ahk
#Include workDir.ahk

class Cd extends BaseHandle {

  static Handle(parsed) {
    if parsed.target = '..' {
      WorkDir.up()
      return this.Succ(WorkDir.dir())
    }
    dirs := WorkDir.getSubDirs(), p := parsed.target
    if !dirs.findIndex(v => v = p) {
      Path.IsAbsolute(p) ? WorkDir.switch(p) : WorkDir.enter(p)
      p := WorkDir.dir()

      if DirExist(p)
        WorkDir.switch(p)
      else return this.Fail('不存在的目录')
    } else WorkDir.enter(p)
    return this.Succ(WorkDir.dir())
  }

  static Spec() {
    return {
      cmd: 'cd',
      desc: '',
      format: 'cd <target>',
      args: {
        desc: '',
        isOptional: false,
        cacheable: false,
        generator: {
          script: '',
          postProcess: getMatchDirs,
          match: match,
          getSg: getSg
        }
      },
      extra: {
        isEnable: false
      }
    }

    getMatchDirs(_, parsed, *) {
      dirs := WorkDir.getSubDirs()
      dirs.Push('..')

      if parsed.target = ''
        return dirs

      cur := WorkDir.dir() ; 记录当前目录

      i := _getIdx(parsed.target)
      if i <= 1
        return dirs

      WorkDir.enter(parsed.target.substring(1, i)) ; 当以 '/' 结尾时，进入此目录
      subs := WorkDir.getSubDirs()

      WorkDir.switch(cur) ; 恢复
      return subs
    }

    match(_, list, loopVal, input) {
      i := _getIdx(input)
      return beginWith(loopVal, i <= 1 ? input : input.substring(i + 1))
    }

    getSg(_, input, sg) {
      i := _getIdx(input), prefix := input.substring(1, i + 1)
      return [
        i <= 1 ? sg : prefix sg,
        i <= 1 ? sg '/' : prefix sg '/'
      ]
    }

    _getIdx(input) {
      i := input.length, chs := input.toChs()
      while i > 0 and chs[i] != '/'
        i--
      return i
    }
  }

}